﻿using Microsoft.AspNetCore.Mvc;
using RuYiAdmin.Net.Common.Global;
using RuYiAdmin.Net.Common.Utility;
using RuYiAdmin.Net.Entity.BusinessDTO.SystemManagement;
using RuYiAdmin.Net.Entity.BusinessEntity.SystemManagement;
using RuYiAdmin.Net.Entity.BusinessEnum;
using RuYiAdmin.Net.Entity.CoreEntity;
using RuYiAdmin.Net.Entity.CoreEnum;
using RuYiAdmin.Net.Service.BusinessService.SystemManagement.Language;
using RuYiAdmin.Net.Service.BusinessService.SystemManagement.Menu;
using RuYiAdmin.Net.Service.BusinessService.SystemManagement.MenuLanguage;
using RuYiAdmin.Net.WebApi.AppCode.Base;
using RuYiAdmin.Net.WebApi.AppCode.Filter;
using System;
using System.Collections.Generic;
using System.Linq;

// For more information on enabling Web API for empty projects, visit https://go.microsoft.com/fwlink/?LinkID=397860

namespace RuYiAdmin.Net.WebApi.Controllers.SystemManagement
{
    /// <summary>
    /// 菜单管理控制器
    /// </summary>
    public class MenuManagementController : BaseController<SysMenu>
    {
        /// <summary>
        /// 菜单服务实例
        /// </summary>
        private readonly IMenuService menuService;

        /// <summary>
        /// 多于服务实例
        /// </summary>
        private readonly ILanguageService languageService;

        /// <summary>
        /// 菜单多语实例
        /// </summary>
        private readonly IMenuLanguageService menuLanguageService;

        /// <summary>
        /// 构造函数
        /// </summary>
        /// <param name="menuService"></param>
        /// <param name="languageService"></param>
        /// <param name="menuLanguageService"></param>
        public MenuManagementController(IMenuService menuService, ILanguageService languageService,
            IMenuLanguageService menuLanguageService) : base(menuService)
        {
            this.menuService = menuService;
            this.languageService = languageService;
            this.menuLanguageService = menuLanguageService;
        }

        /// <summary>
        /// 查询菜单列表
        /// </summary>
        /// <param name="queryCondition">查询条件</param>
        /// <returns>ActionResult</returns>
        [HttpPost]
        [Log(OperationType.QueryList)]
        [Permission("menu:query:list")]
        public IActionResult Post(QueryCondition queryCondition)
        {
            var actionResult = this.menuService.GetMenuTreeNodes();
            return Ok(actionResult);
        }

        /// <summary>
        /// 获取菜单信息
        /// </summary>
        /// <param name="id">编号</param>
        /// <returns>ActionResult</returns>
        [HttpGet("{id}")]
        [Log(OperationType.QueryEntity)]
        [Permission("menu:query:list")]
        public IActionResult GetById(Guid id)
        {
            var actionResult = this.menuService.GetById(id);
            return Ok(actionResult);
        }

        /// <summary>
        /// 新增码表信息
        /// </summary>
        /// <param name="sysMenu">菜单对象</param>
        /// <returns>ActionResult</returns>
        [HttpPost]
        [Log(OperationType.AddEntity)]
        [Permission("menu:add:entity")]
        public IActionResult Add([FromBody] SysMenuDTO sysMenu)
        {
            var actionResult = this.menuService.Add(sysMenu);
            if (!String.IsNullOrEmpty(sysMenu.MenuNameEn))
            {
                var language = (this.languageService.GetList().Object as List<SysLanguage>).Where(t => t.LanguageName.Equals("en-US")).FirstOrDefault();

                var menuLan = new SysMenuLanguage();
                menuLan.LanguageId = language.Id;
                menuLan.MenuId = sysMenu.Id;
                menuLan.MenuName = sysMenu.MenuNameEn;
                this.menuLanguageService.Add(menuLan);
            }
            if (!String.IsNullOrEmpty(sysMenu.MenuNameRu))
            {
                var language = (this.languageService.GetList().Object as List<SysLanguage>).Where(t => t.LanguageName.Equals("ru-RU")).FirstOrDefault();

                var menuLan = new SysMenuLanguage();
                menuLan.LanguageId = language.Id;
                menuLan.MenuId = sysMenu.Id;
                menuLan.MenuName = sysMenu.MenuNameRu;
                this.menuLanguageService.Add(menuLan);
            }
            return Ok(actionResult);
        }

        /// <summary>
        /// 修改菜单信息
        /// </summary>
        /// <param name="sysMenu">菜单对象</param>
        /// <returns>IActionResult</returns>
        [HttpPut]
        [Log(OperationType.EditEntity)]
        [Permission("menu:edit:entity")]
        public IActionResult Put([FromBody] SysMenuDTO sysMenu)
        {
            var actionResult = this.menuService.Update(sysMenu);
            if (!String.IsNullOrEmpty(sysMenu.MenuNameEn))
            {
                var language = (this.languageService.GetList().Object as List<SysLanguage>).Where(t => t.LanguageName.Equals("en-US")).FirstOrDefault();

                var oldMenuLan = (this.menuLanguageService.GetList().Object as List<SysMenuLanguage>).
                    Where(t => t.LanguageId.Equals(language.Id) && t.MenuId.Equals(sysMenu.Id) && t.IsDel.Equals(0)).FirstOrDefault();

                if (oldMenuLan != null)
                {
                    this.menuLanguageService.Delete(oldMenuLan.Id);
                }

                var menuLan = new SysMenuLanguage();
                menuLan.LanguageId = language.Id;
                menuLan.MenuId = sysMenu.Id;
                menuLan.MenuName = sysMenu.MenuNameEn;
                this.menuLanguageService.Add(menuLan);
            }
            if (!String.IsNullOrEmpty(sysMenu.MenuNameRu))
            {
                var language = (this.languageService.GetList().Object as List<SysLanguage>).Where(t => t.LanguageName.Equals("ru-RU")).FirstOrDefault();

                var oldMenuLan = (this.menuLanguageService.GetList().Object as List<SysMenuLanguage>).
                    Where(t => t.LanguageId.Equals(language.Id) && t.MenuId.Equals(sysMenu.Id) && t.IsDel.Equals(0)).FirstOrDefault();

                if (oldMenuLan != null)
                {
                    this.menuLanguageService.Delete(oldMenuLan.Id);
                }

                var menuLan = new SysMenuLanguage();
                menuLan.LanguageId = language.Id;
                menuLan.MenuId = sysMenu.Id;
                menuLan.MenuName = sysMenu.MenuNameRu;
                this.menuLanguageService.Add(menuLan);
            }
            return Ok(actionResult);
        }

        /// <summary>
        /// 删除菜单信息
        /// </summary>
        /// <param name="id">编号</param>
        /// <returns>ActionResult</returns>
        [HttpDelete("{id}")]
        [Log(OperationType.DeleteEntity)]
        [Permission("menu:del:entities")]
        public IActionResult Delete(Guid id)
        {
            if (this.Check(id))
            {
                return BadRequest("menu contains subitems,can not be deleted.");
            }
            var actionResult = this.menuService.Delete(id);

            var oldMenuLans = (this.menuLanguageService.GetList().Object as List<SysMenuLanguage>).
                    Where(t => t.MenuId.Equals(id) && t.IsDel.Equals(0));
            if (oldMenuLans != null)
            {
                this.menuLanguageService.DeleteRange(oldMenuLans.Select(t => t.Id).ToArray());
            }

            return Ok(actionResult);
        }

        /// <summary>
        /// 批量删除菜单信息
        /// </summary>
        /// <param name="ids">数组串</param>
        /// <returns>ActionResult</returns>
        [HttpDelete("{ids}")]
        [Log(OperationType.DeleteEntity)]
        [Permission("menu:del:entities")]
        public IActionResult DeleteRange(String ids)
        {
            var array = StringUtil.GetGuids(ids);
            foreach (var item in array)
            {
                if (this.Check(item))
                {
                    return BadRequest("code contains subitems,can not be deleted.");
                }
            }
            var actionResult = this.menuService.DeleteRange(array);

            foreach (var item in array)
            {
                var oldMenuLans = (this.menuLanguageService.GetList().Object as List<SysMenuLanguage>).
                    Where(t => t.MenuId.Equals(item) && t.IsDel.Equals(0));
                if (oldMenuLans != null)
                {
                    this.menuLanguageService.DeleteRange(oldMenuLans.Select(t => t.Id).ToArray());
                }
            }

            return Ok(actionResult);
        }

        /// <summary>
        /// 机构检测
        /// </summary>
        /// <param name="parentId">父键</param>
        /// <returns>真假值</returns>
        private bool Check(Guid parentId)
        {
            var queryCondition = new QueryCondition();
            queryCondition.QueryItems = new List<QueryItem>();
            queryCondition.QueryItems.Add(new QueryItem()
            {
                Field = "ParentId",
                DataType = DataType.Guid,
                QueryMethod = QueryMethod.Equal,
                Value = parentId
            });

            var strSQL = GlobalContext.Configuration.GetSection("sqls:sql:query_sysmenu").Value.Replace("AND isnull(ParentId)=1", "");

            var data = this.menuService.SqlQuery<SysMenuDTO>(strSQL, queryCondition);

            if (data.List.Count > 0)
            {
                return true;
            }

            return false;
        }
    }
}
